package com.rdc.example.service.impl;

import com.rdc.example.bean.PageBean;
import com.rdc.example.bean.Result;
import com.rdc.example.bean.dto.UserDTO;
import com.rdc.example.dao.impl.PlayListDaoImpl;
import com.rdc.example.dao.impl.UserDaoImpl;
import com.rdc.example.entity.PlayList;
import com.rdc.example.entity.User;
import com.rdc.example.service.UserService;
import com.rdc.example.util.HashUtil;
import org.apache.commons.fileupload.FileItem;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.*;

import static com.rdc.example.util.CheckCodeUtil.generateVerifyCode;
import static com.rdc.example.util.EmialUtil.sendEmail;
import static com.rdc.example.util.FileUtil.uploadFile;

/**
 * @author duck
 * @description 用户service业务层接口实现类
 */
public class UserServiceImpl implements UserService {

    UserDaoImpl userDao = new UserDaoImpl();
    PlayListDaoImpl playListDao = new PlayListDaoImpl();

//    public static void main(String[] args) throws Exception {
//
//
//
//    }


    @Override
    public Result login(String userName, String password) throws Exception {
        boolean login = userDao.login(userName, password);
        return login ? Result.success("登录成功", null)
                : Result.fail("登录失败", null);
    }


    @Override
    public Result insertUser(UserDTO userDTO,List<FileItem> fileItems) throws Exception {
        User user=convertToEntity(userDTO);
        Result result=uploadFile(fileItems,0);
        if(result.getCode()==200){
            //如果上传成功，就存入user
            user.setAvatarPath((String) result.getData());
        } System.out.println(result);
        boolean insertUser = userDao.insert(user);
        if(insertUser){
            //创建对应的红心歌单
            User userNow=userDao.getUserByUserName(user.getUserName());
            PlayList playList=new PlayList();
            playList.setUserId(userNow.getId());
            playList.setName(userNow.getUserName()+"的红心歌单");
            playList.setCoverPath("imgs/redHeart.png");
            playList.setIsLike(1);
            boolean insertPlayList= playListDao.insert(playList);
            return insertPlayList ?Result.success("注册成功", null)
                    : Result.fail("注册失败", null);
        }
        return Result.fail("注册失败", null);
    }

    @Override
    public Boolean checkUserName(String userName) throws Exception {
        if(userName==null || userName.isEmpty()){
            return false;
        }
        return userDao.checkName(userName);
    }

    @Override
    public Result updateUser(UserDTO userDTO) throws Exception {
        if(userDTO==null){
            return Result.fail("用户为空", null);
        }
        User user=convertToEntity(userDTO);
        boolean update= userDao.update(user);
        return update?Result.success("修改成功", null)
                : Result.fail("修改失败", null);
    }

    @Override
    public Result updateUser(UserDTO userDTO, List<FileItem> fileItems) throws Exception {
        if(userDTO==null){
            return Result.fail("用户为空", null);
        }
        User user=convertToEntity(userDTO);
        //获取头像路径
        Result headResult=uploadFile(fileItems,0);
        if(headResult.getCode()==200){
            //获取成功，存入user
            user.setAvatarPath(headResult.getData().toString());
        }else {
            //获取失败，返回headResult失败结果
            return Result.fail(headResult.getMessage(), null);
        }
        boolean update= userDao.update(user);
        return update?Result.success("修改成功", null)
                : Result.fail("修改失败", null);
    }

    @Override
    public Result updateUserToMusicer(Integer userId) throws Exception {
        if(userId==null){
            return Result.fail("用户为空", null);
        }
        //1 普通用户 2 音乐人 3 管理员
        boolean update= userDao.updateUserType(userId,2);
        return update?Result.success("修改成功", null)
                : Result.fail("修改失败", null);
    }

    @Override
    public Result updateUserToManager(Integer userId) throws Exception {
        if(userId==null){
            return Result.fail("用户为空", null);
        }
        //1 普通用户 2 音乐人 3 管理员
        boolean update= userDao.updateUserType(userId,3);
        return update?Result.success("修改成功", null)
                : Result.fail("修改失败", null);
    }

    @Override
    public Result updateUserWallet(Integer userId, BigDecimal changeValue) throws Exception {
        if(userId==null){
            return Result.fail("userId为空", null);
        }
        boolean update= userDao.updateUserWallet(userId,changeValue);
        return update?Result.success("修改成功", null)
                : Result.fail("修改失败", null);
    }

    @Override
    public Result updateUserVipEndAt(Integer userId, Integer days) throws Exception {
        if (userId == null || days == null) {
            return Result.fail("用户ID和天数不能为空",null);
        }
        // 定义天数与金额映射表
        Map<Integer, BigDecimal> dayPriceMap = new HashMap() {{
            put(1,   new BigDecimal("1"));
            put(30,  new BigDecimal("10"));
            put(90,  new BigDecimal("25"));
            put(180, new BigDecimal("50"));
            put(360, new BigDecimal("80"));
        }};
        // 验证天数有效性
        if (!dayPriceMap.containsKey(days)) {
            return Result.fail("不支持该天数套餐",null);
        }
        // 获取用户信息
        User user = userDao.getUserById(userId);
        if (user == null) {
            return Result.fail("用户不存在",null);
        }
        // 金额校验
        BigDecimal cost = dayPriceMap.get(days);
        if (user.getWallet().compareTo(cost) < 0) {
            return Result.fail("余额不足，需要支付：" + cost + "元",null);
        }
        try {
            // 扣费操作  cost.negate()的负数
            //System.out.println( cost.negate());
            userDao.updateUserWallet(userId,  cost.negate());
            // 计算新VIP时间
            LocalDateTime newEnd = user.getVipEndAt() != null && user.getVipEndAt().isAfter(LocalDateTime.now())
                    ? user.getVipEndAt().plusDays(days)
                    : LocalDateTime.now().plusDays(days);
            // 更新有效期
            userDao.updateUserVipEndAt(userId, newEnd);
            return Result.success("成功续期" + days + "天", newEnd);
        } catch (Exception e) {
            // 简易回滚机制
            userDao.updateUserWallet(userId, cost);
            return Result.fail("交易失败，已恢复余额",null);
        }
    }

    @Override
    public Result setCodeToEmail(String userName) throws Exception {
        User user =userDao.getUserByUserName(userName);
        if(user==null||user.getEmail()==null){
            return Result.fail("没有对应用户或对应用户没有邮箱",null);
        }
        //获取4位验证码
        String code=generateVerifyCode(4);
        System.out.println("code:"+code);
        //发送邮件
        String message="【lijialiang_Cloudmusic】帐号名称："+user.getUserName()
                +" 于 "+LocalDateTime.now()
                +" 在使用邮箱验证修改密码。邮箱验证码"
                +code+"如非本人操作，请忽略本短信。";
        boolean send= sendEmail(user.getEmail(),"邮箱验证修改密码",message);
        return send?Result.success("发送成功",code):
                Result.fail("发送失败",null);
    }

    @Override
    public Result updatePassword(String userName, String password) throws Exception {
        User user = userDao.getUserByUserName(userName);
        if(user==null){
            return Result.fail("没有对应用户",null);
        }
        //密码加密
        String hashedPassword = HashUtil.getSaltMD5(password);
        user.setPasswordHash(hashedPassword);
        //更新
        boolean update= userDao.update(user);
        return update?Result.success("更新成功",null)
                :Result.fail("更新失败",null);
    }




    @Override
    public UserDTO getUserById(Integer id) throws Exception {
        if(id==null){
            return null;
        }
        User user=userDao.getUserById(id);
        return convertToDto(user);
    }

    @Override
    public UserDTO getUserByUserName(String name) throws Exception {
        User user=userDao.getUserByUserName(name);
        return convertToDto(user);
    }

    @Override
    public PageBean<UserDTO> searchUsersByUsername(String keyword, Integer currentPage, Integer pageSize) throws Exception {
        Integer pageBegin = (currentPage - 1) * pageSize;
        // 调用 dao
        List<User> userList =userDao.searchUsersByUsername(keyword, pageBegin, pageSize);
        Integer totalCount = userDao.countSearchUsersByUsername(keyword);
        // 封装 PageBean
        PageBean<UserDTO> pageBean = new PageBean<>();
        pageBean.setTotalCount(totalCount);
        pageBean.setRows(convertUsers(userList));
        return pageBean;
    }


    //entity -->dto 密码不传
    public UserDTO convertToDto(User entity) {
        UserDTO dto = new UserDTO();
        dto.setId(entity.getId());
        dto.setUserName(entity.getUserName());
        dto.setPhone(entity.getPhone());
        //密码传不了
        dto.setEmail(entity.getEmail());
        dto.setAvatarPath(entity.getAvatarPath());
        dto.setUserType(entity.getUserType());
        dto.setWallet(entity.getWallet());
        dto.setVipEndAt(entity.getVipEndAt());
        dto.setCreatedAt(entity.getCreatedAt());
        return dto;
    }

    // dto -->entity 密码进行加密
    public User convertToEntity(UserDTO dto) {
        User entity = new User();
        entity.setId(dto.getId());
        entity.setUserName(dto.getUserName());
        //密码md5加盐加密
        String hashedPassword = HashUtil.getSaltMD5(dto.getPassword());
        entity.setPasswordHash(hashedPassword);
        entity.setPhone(dto.getPhone());
        entity.setEmail(dto.getEmail());
        entity.setAvatarPath(dto.getAvatarPath());
        entity.setUserType(dto.getUserType());
        entity.setWallet(dto.getWallet());
        entity.setVipEndAt(dto.getVipEndAt());
        entity.setCreatedAt(dto.getCreatedAt());
        return entity;
    }

    private List<UserDTO> convertUsers(List<User> entityList) {
        List<UserDTO> dtos = new ArrayList<>();
        for(User entity:entityList){
            dtos.add(convertToDto(entity));
        }
        return dtos;
    }


}
